/*
 * Created by Jaren at 2021/10/29 15:55
 */
import 'dart:typed_data';

import 'package:binary/binary.dart';
import 'package:inmotion_protocol/common/compact.dart';
import 'package:inmotion_protocol/common/product_model.dart';
import 'package:inmotion_protocol/common/product_version.dart';
import 'package:inmotion_protocol/lorin/bean/scooter/scooter_settings.dart';
import 'package:inmotion_protocol/lorin/factory/special/scooter/c1_message_factory.dart';
import 'package:inmotion_protocol/util/byte_util.dart';

class C1Settings extends ScooterSettings {
  static const int assistModeMinSpeed = 200; // 行人模式可调限速最小值
  static const int assistModeMaxSpeed = 600; // 行人模式可调限速最大值

  Uint16 limitSpeedOfAssistMode = Uint16.zero;

  C1Settings(ProductModel model, VersionWrapper version) : super(model, version);

  @override
  void initCompact() {
    compact = DefaultC1Settings();
  }

  /// C1 Pro骑行模式定义不同
  /// see [C1MessageFactory.genSetRidingModeMsg]
  @override
  RidingMode toRidingMode(int mode) {
    if (!model.isLC1Pro()) return super.toRidingMode(mode);
    switch (mode) {
      case 1:
        return RidingMode.normal;
      case 2:
        return RidingMode.sport;
      case 0:
      default:
        return RidingMode.assist;
    }
  }

  @override
  String toString() {
    return 'C1Settings{compact: $compact, zeroStartupState: $zeroStartupState, cruiseState: $cruiseState, '
        'speedUnit: $speedUnit, ridingMode: $ridingMode, lockMode: $lockMode, safeSpeedState: $safeSpeedLimitState, '
        'accelerateForce: $accelerateForce, brakeForce: $brakeForce, limitSpeed: $limitSpeed}';
  }
}

class DefaultC1Settings extends Compact<C1Settings> {
  @override
  void fromBytes(C1Settings output, Uint8ClampedList bytes, int offset) {
    output.zeroStartupState = ByteUtil.bitValue(bytes[offset], 0, 1);
    output.cruiseState = ByteUtil.bitValue(bytes[offset], 1, 1);
    output.speedUnit = ByteUtil.bitValue(bytes[offset], 2, 1);
    output.ridingMode = output.toRidingMode(ByteUtil.bitValue(bytes[offset], 3, 3).value);
    output.lockMode = ByteUtil.bitValue(bytes[offset], 6, 1);
    // 剩余1bit保留
    offset++;
    // 保留3bit
    output.safeSpeedLimitState = ByteUtil.bitValue(bytes[offset], 3, 1);
    // 剩余4bit保留
    offset++;
    output.accelerateForce = ByteUtil.bytes2Uint8Le(bytes, offset);
    offset++;
    output.brakeForce = ByteUtil.bytes2Uint8Le(bytes, offset);
    offset++;
    output.limitSpeed = ByteUtil.bytes2Uint16Le(bytes, offset);
    offset += 2;
    output.limitSpeedOfAssistMode = ByteUtil.bytes2Uint16Le(bytes, offset);
  }

  @override
  int length() {
    return 6;
  }
}
